/*
    Bandleader
    Copyright (c) 2006 by Grant Yoshida

    Licensed under the GPL version 2 or later,
    please see COPYING for details.
*/

#ifndef ChordView_h
#define ChordView_h

#include "Cursor.h"
#include "CursorHost.h"
#include "PtrFwd.h"
#include <QtGui/QWidget>

class MidiPlayer;
class QUndoStack;
class QTextStream;

class ChordView : public QWidget,
                  public CursorHost
{
    Q_OBJECT
public:
    ChordView(const DocumentPtr &document, QWidget *parent = 0);

    DocumentPtr getDocument() const;

    void setCursorPosition(int index);

    int numRows() const;
    int numCols() const;

    QUndoStack *undoStack() const;

    QSize sizeHint() const;

    //

    int indexOfRow(int row) const;
    int indexOf(int row, int col) const;

    int rowOfIndex(int index) const;
    int colOfIndex(int index) const;

    int cellsPerRow() const;

signals:
    void playingStateChanged(bool playing);

public slots:
    void deleteBar();
    void insertBar();
    void insertBarAfter();
    void openRow();
    void deleteRow();
    void copy();
    void paste();
    void cut();
    void deleteSelection();

    void save();
    void saveAs();

    void togglePlaying();
    void play();
    void stop();

    void handleStoppedPlaying();

private slots:
    void updatePlayCursor();

private:
    void paintEvent(QPaintEvent *event);
    void keyPressEvent(QKeyEvent *event);
    void mousePressEvent(QMouseEvent *event);
    void focusInEvent(QFocusEvent *event);
    void contextMenuEvent(QContextMenuEvent *event);

private:
    void computeCellDimensions(QPainter &painter);

    void moveCursorLeft();
    void moveCursorRight();
    void moveCursorUp();
    void moveCursorDown();

    void wordLeft();
    void wordRight();

    void generateMidiFile();
    void playMidiFile(const QString &fileName);

    // Pseudo signals
    void startedPlaying();
    void stoppedPlaying();

    void msgBox(const QString &message);

    // primitives
    void setChord(int index, const QString &chord);
    void deleteChord(int index);
    void insertBar(int index);
    void insertBarAfter(int index);
    void deleteBar(int index);
    void openRow(int index);
    void deleteRow(int index);

    void appendInput(const QString &text);
    void backspace();
    void commitInput();
    void endInput();

    void deleteChordUnderCursor();

    void drawChords(QPainter &painter);
    void drawRow(QPainter &painter, int row, const QStringList &chords);
    void drawCell(QPainter &painter, const QStringList &chords, int x, int y);

    void colorCell(QPainter &painter, int row, int col,
                   const QBrush &brush, const QPen &pen);
    void drawCursor(QPainter &painter);
    void drawPlayCursor(QPainter &painter);

    void drawCommandLine(QPainter &painter);

    void drawSelection(QPainter &painter);

    void setBackgroundColor();

    int virtualWidth() const;
    int virtualHeight() const;

private:
    //! Chords
    DocumentPtr m_document;

    //
    QUndoStack *m_undoStack;

    //
    MidiPlayer *m_midiPlayer;

    //
    QString m_midiFileName;

    //
    Cursor m_cursor;

    //
    Cursor m_playCursor;

    //
    QString m_inputText;

    //
    bool m_editingText;

    //
    int m_inputCellIndex;

    //
    QVector<QPoint> m_selectionSet;

    //! Beats per measure
    int m_divisionsPerCell;

    int m_cellsPerRow;

    //! Cached value
    int m_columnsPerRow;

    int m_cellWidth;
    int m_cellHeight;

    int m_divisionWidth;
    int m_divisionHeight;
};

#endif
